package edu.pku.sei.modeler.model.notation.shape;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;

import org.eclipse.draw2d.geometry.Point;
import org.eclipse.swt.SWT;
import org.w3c.dom.Element;

import edu.pku.sei.gefcommon.descriptor.annotation.EnumerationProperty;
import edu.pku.sei.gefcommon.descriptor.annotation.MethodProperty;
import edu.pku.sei.modeler.model.notation.core.NotationPackage;
import edu.pku.sei.modeler.model.notation.core.ShapeConstance;
import edu.pku.sei.modeler.model.notation.core.ShapeNode;
import edu.pku.sei.modeler.model.xml.XMLUtility;

public class ConnectionTemplate extends ShapeNode {
	static final public int END_NONE = 0;
	static final public int END_ARROW= 1; 
	static final public int END_TRIANGLE = 2;
	static final public int END_DIAMOND = 3;
	static final public int END_SOLIDTRIANGLE = 4;
	static final public int END_SOLIDDIAMOND = 5;
	static final private String[] lineStyles = new String[]{
		"Solid","Dash","Dot","DashDot","DashDotDot","Custom"
	};
	static final private String[] endStyles = new String[]{
		"None","Arrow","Triangle","Diamond","SolidTriangle","SolidDiamond"
	};
	
	private Point startPoint;
	private Point endPoint;
	private int lineStyle;
	private int endStyle;
	
	public ConnectionTemplate(){
		startPoint = new Point(0,0);
		endPoint = new Point(100,100);
		lineStyle = org.eclipse.swt.SWT.LINE_SOLID;
		endStyle = END_NONE;
	}
	public void setStartPoint(int x,int y) {
		this.startPoint.setLocation(x, y);
		this.firePropertyChange(ShapeConstance.REFRESH_VIEW, null, startPoint);
	}
	public Point getStartPoint() {
		return startPoint;
	}
	public void setEndPoint(int x,int y) {
		this.endPoint.setLocation(x, y);
		this.firePropertyChange(ShapeConstance.REFRESH_VIEW, null, endPoint);
	}
	
	public Point getEndPoint() {
		return endPoint;
	}
	
	public int getLineStyle() {
			return lineStyle;
	}
	
	public void setLineStyle(int lineStyle) {
		if (lineStyle == org.eclipse.swt.SWT.LINE_SOLID 
				|| lineStyle == org.eclipse.swt.SWT.LINE_DASH
				|| lineStyle == org.eclipse.swt.SWT.LINE_CUSTOM
				|| lineStyle == org.eclipse.swt.SWT.LINE_DASHDOT
				|| lineStyle == org.eclipse.swt.SWT.LINE_DASHDOTDOT
				|| lineStyle == org.eclipse.swt.SWT.LINE_DOT) {
			int oldValue = this.lineStyle;
			this.lineStyle = lineStyle;
			this.firePropertyChange(ShapeConstance.REFRESH_VIEW, oldValue, this.lineStyle);
			
		}
	}
	
	public int getEndStyle() {
			return endStyle;
	}
	public void setEndStyle(int endStyle) {
		if (endStyle >= END_NONE && endStyle <= END_SOLIDDIAMOND) {
			int oldValue = this.endStyle; 
			this.endStyle = endStyle;
			this.firePropertyChange(ShapeConstance.REFRESH_VIEW, oldValue, this.endStyle);
			
		}
	}
	
	public String [] getLineStyles() {
		return lineStyles;
	}
	public String [] getEndStyles() {
		return endStyles;
	}
	@MethodProperty(
			id = "CONNECTION_END_STYLE",
			catalog = "Connection",
			name = "End Style",
			setter = "setEndStyleStr")
	@EnumerationProperty(
			function = "getEndStyles"
	)
	public String getEndStyleStr() {
		if (endStyle == END_NONE) {
			return "None";
		}
		else if(endStyle == END_ARROW) {
			return "Arrow";
		}
		else if(endStyle == END_TRIANGLE) {
			return "Triangle";
		}
		else if(endStyle == END_DIAMOND) {
			return "Diamond";
		}
		else if(endStyle == END_SOLIDTRIANGLE) {
			return "SolidTriangle";
		}
		else if(endStyle == END_SOLIDDIAMOND) {
			return "SolidDiamond";
		}
		return "";
	}
	public void setEndStyleStr(String style) {
		if("None".equals(style)) {
			setEndStyle(END_NONE);
		}
		else if("Arrow".equals(style)) {
			setEndStyle(END_ARROW);
		}
		else if("Triangle".equals(style)) {
			setEndStyle(END_TRIANGLE);
		}
		else if("Diamond".equals(style)) {
			setEndStyle(END_DIAMOND);
		}
		else if("SolidTriangle".equals(style)) {
			setEndStyle(END_SOLIDTRIANGLE);
		}
		else if("SolidDiamond".equals(style)) {
			setEndStyle(END_SOLIDDIAMOND);
		}
	}
	@MethodProperty(
			id = "CONNECTION_LINE_STYLE",
			catalog = "Connection",
			name = "Line Style",
			setter = "setLineStyleStr")
	@EnumerationProperty(
			function = "getLineStyles"
	)
	public String getLineStyleStr() {
		if (lineStyle == org.eclipse.swt.SWT.LINE_SOLID) {
			return "Solid";
		}
		else if(lineStyle == org.eclipse.swt.SWT.LINE_DASH) {
			return "Dash";
		}
		else if(lineStyle == org.eclipse.swt.SWT.LINE_CUSTOM) {
			return "Custom";
		}
		else if(lineStyle == org.eclipse.swt.SWT.LINE_DASHDOT) {
			return "DashDot";
		}
		else if(lineStyle == org.eclipse.swt.SWT.LINE_DASHDOTDOT) {
			return "DashDotDot";
		}
		else if(lineStyle == org.eclipse.swt.SWT.LINE_DOT) {
			return "Dot";
		}
		return "";
	}
	public void setLineStyleStr(String style) {
		if("Solid".equals(style)) {
			setLineStyle(SWT.LINE_SOLID);
		}
		else if("Dash".equals(style)) {
			setLineStyle(SWT.LINE_DASH);
		}
		else if("Dot".equals(style)) {
			setLineStyle(SWT.LINE_DOT);
		}
		else if("DashDot".equals(style)) {
			setLineStyle(SWT.LINE_DASHDOT);
		}
		else if("DashDotDot".equals(style)) {
			setLineStyle(SWT.LINE_DASHDOTDOT);
		}
		else if("Custom".equals(style)) {
			setLineStyle(SWT.LINE_CUSTOM);
		}
	}
	//add by fengchao
	public void serialize(Element root) {
		super.serialize(root);
		XMLUtility.xmlInstance.serializeAttribute(root, NotationPackage.CONNECTION_STARTPOINT_X, startPoint.x);
		XMLUtility.xmlInstance.serializeAttribute(root, NotationPackage.CONNECTION_STARTPOINT_Y, startPoint.y);
		XMLUtility.xmlInstance.serializeAttribute(root, NotationPackage.CONNECTION_ENDPOINT_X, endPoint.x);
		XMLUtility.xmlInstance.serializeAttribute(root, NotationPackage.CONNECTION_ENDPOINT_Y, endPoint.y);
		XMLUtility.xmlInstance.serializeAttribute(root, NotationPackage.CONNECTION_LINESTYLE, lineStyle);
		XMLUtility.xmlInstance.serializeAttribute(root, NotationPackage.CONNECTION_ENDSTYLE, endStyle);
	}
	public void deSerialize(Element root) {
		super.deSerialize(root);
		int startPointX = XMLUtility.xmlInstance.deSerializeInt(root, NotationPackage.CONNECTION_STARTPOINT_X);
		int startPointY = XMLUtility.xmlInstance.deSerializeInt(root, NotationPackage.CONNECTION_STARTPOINT_Y);
		this.startPoint = new Point(startPointX, startPointY);
		int endPointX = XMLUtility.xmlInstance.deSerializeInt(root, NotationPackage.CONNECTION_ENDPOINT_X);
		int endPointY = XMLUtility.xmlInstance.deSerializeInt(root, NotationPackage.CONNECTION_ENDPOINT_Y);
		this.endPoint = new Point(endPointX, endPointY);
		this.lineStyle = XMLUtility.xmlInstance.deSerializeInt(root, NotationPackage.CONNECTION_LINESTYLE);
		this.endStyle = XMLUtility.xmlInstance.deSerializeInt(root, NotationPackage.CONNECTION_ENDSTYLE);
	}
	//end add
	
}
